﻿//using System;
//using System.Collections.Generic;
//using System.Linq;
//using System.Text;
//using Microsoft.Xna.Framework.Graphics;
//using RAD;
//using Microsoft.Xna.Framework;
//using Red;
//using System.Runtime.InteropServices;
//using Microsoft.Xna.Framework.Graphics.PackedVector;
//using System.Yaml;

//namespace TriExporterNET.Engine
//{

//    class EVEMesh
//    {
//        public List<EVEMeshPart> meshParts = new List<EVEMeshPart>();
//        public Dictionary<string, Texture> textures = new Dictionary<string, Texture>();
//        GraphicsDevice GraphicsDevice = null;


//        public Vector3 modelCenter;
//        public float modelRadius;
//        public static TextureCube cube;
//        static Random rnd = new Random((int)DateTime.Now.Ticks);

//        BasicEffect effect;
//        public EVEMesh(GraphicsDevice device, string redfile, List<Stuff.StuffFileEntry> List)
//        {
//            GraphicsDevice = device;
//            effect = new BasicEffect(device);
//            if (cube != null)
//            {
//                cube.Dispose();
//            }
//            var sfcl = List.Where(x => x.FullName.EndsWith("_cube.dds") && x.FullName.Contains("universe")).ToList();
//            bool badcube = true;
//            while (badcube)
//            {
//                var sfc = sfcl[rnd.Next(0, sfcl.Count - 1)];
//                if (sfc != null)
//                {
//                    using (var stream = sfc.GetStream())
//                    {
//                        AlphaSubmarines.DDSLib.DDSFromStream(stream, device, 0, false, out  cube);
//                        if (cube != null)
//                            badcube = false;
//                    }
//                }
//            }

//            var sfred = List.FirstOrDefault(x => x.FullName == redfile);
//            YamlMapping redobject;
//            using (var stream = sfred.GetStream())
//            {
//                redobject = YamlNode.FromYaml(stream)[0] as YamlMapping;
//            }
//            YamlMapping mesh = null;
//            try
//            {
//                mesh = (redobject["highDetailMesh"] as YamlMapping)["object"] as YamlMapping;
//            }
//            catch { }
//            if (mesh == null)
//                try
//                {
//                    mesh = redobject["mesh"] as YamlMapping;
//                }
//                catch { }
//            string grfile = (mesh["geometryResPath"] as YamlScalar).Value;
//            grfile = grfile.Replace(":", "").Replace("/", "\\").Replace("\"", "").ToLower();
//            var sfgr = List.FirstOrDefault(x => x.FullName == grfile);
//            var bytes = sfgr.GetBytes();
//            var gf = GrannyInterop.GrannyReadEntireFileFromMemory(bytes.Length, bytes);
//            var fip = GrannyInterop.GrannyGetFileInfo(gf);
//            var fi = fip.Convert<gFileInfo>();
//            var mpp = fi.Meshes.Convert<IntPtr>();
//            var mp = mpp.Convert<Mesh>();
//            var vc = GrannyInterop.GrannyGetMeshVertexCount(mpp);
//            var bpi = GrannyInterop.GrannyGetMeshBytesPerIndex(mpp);
//            var ic = GrannyInterop.GrannyGetMeshIndexCount(mpp);
//            var tgc = GrannyInterop.GrannyGetMeshTriangleGroupCount(mpp);
//            var tgp = GrannyInterop.GrannyGetMeshTriangleGroups(mpp);

//            IEnumerable<EVEMeshPart> parts = null;
//            var inds = new int[ic];
//            var handle = GCHandle.Alloc(inds, GCHandleType.Pinned);
//            GrannyInterop.GrannyCopyMeshIndices(mpp, Marshal.SizeOf(inds[0]), handle.AddrOfPinnedObject());
//            handle.Free();
//            IndexBuffer = new IndexBuffer(device, inds[0].GetType(), ic, BufferUsage.WriteOnly);
//            IndexBuffer.SetData(inds, 0, ic);
//            parts = Enumerable.Range(0, tgc).Select(x => IntPtr.Add(tgp, Marshal.SizeOf(typeof(Groups)) * x).Convert<Groups>()).Select(tg =>
//            {
//                return new EVEMeshPart() { TriangleCount = tg.TriCount, TriangleFirst = tg.TriFirst * 3 };
//            }).ToArray();
//            meshParts.AddRange(parts);

//            VertexCount = vc;


//            MVPTNTB[] vces = new MVPTNTB[vc];
//            handle = GCHandle.Alloc(vces, GCHandleType.Pinned);
//            GrannyInterop.GrannyCopyMeshVertices(mpp, GrannyInterop.GrannyPNGBT33332VertexType.Convert<IntPtr>(), handle.AddrOfPinnedObject());
//            handle.Free();
//            vertexBuffer = new VertexBuffer(device, typeof(MVPTNTB), vc, BufferUsage.WriteOnly);
//            vertexBuffer.SetData<MVPTNTB>(vces);
//            GrannyInterop.GrannyFreeFile(gf);
//            IEnumerable<Tuple<YamlMapping, bool>> areas = (mesh["opaqueAreas"] as YamlSequence).Cast<YamlMapping>().Select(x => new Tuple<YamlMapping, bool>(x, false));
//            try
//            {
//                areas = areas.Union((mesh["transparentAreas"] as YamlSequence).Cast<YamlMapping>().Select(x => new Tuple<YamlMapping, bool>(x, true)));
//            }
//            catch { }
//            try
//            {
//                areas = areas.Union((mesh["decalAreas"] as YamlSequence).Cast<YamlMapping>().Select(x => new Tuple<YamlMapping, bool>(x, false)));
//            }
//            catch { }
//            //(((List<dynamic>)mesh.transparentAreas).Select(x => { x.isTransparent = true; return x; })).Union
//            //(((List<dynamic>)mesh.decalAreas).Select(x => { x.isTransparent = false; return x; })));
//            foreach (var area in areas)
//            {
//                int i = 0;
//                try
//                {
//                    i = int.Parse((area.Item1["index"] as YamlScalar).Value);
//                }
//                catch { }
//                if (i >= meshParts.Count)
//                    continue;
//                var effect1 = area.Item1["effect"] as YamlMapping;
//                var resources = effect1["resources"] as YamlSequence;
//                var parameters = effect1["parameters"] as YamlSequence;//((List<dynamic>)area.effect.parameters);
//                meshParts[i].IsTransparent = area.Item2;//(bool)area.isTransparent;
//                //dynamic dif = ;
//                var difs = ((resources.Cast<YamlMapping>().FirstOrDefault(x => (x["name"] as YamlScalar).Value == "DiffuseMap"))["resourcePath"] as YamlScalar).Value
//                    .Replace(":", "").Replace("/", "\\").Replace("\"", "").ToLower();

//                if (!textures.ContainsKey(difs))
//                {
//                    var sf = List.FirstOrDefault(x => x.FullName == difs);
//                    if (sf != null)
//                        using (var stream = sf.GetStream())
//                        {
//                            Texture2D tex = null;
//                            AlphaSubmarines.DDSLib.DDSFromStream(stream, device, 0, false, out  tex);
//                            textures[difs] = tex;
//                            //textures[difs] = DDSSuport.Load(GraphicsDevice, stream);
//                        }
//                }
//                if (textures.ContainsKey(difs))
//                    meshParts[i].DiffuseMap = difs;
//                var glow = resources.Cast<YamlMapping>().FirstOrDefault(x => (x["name"] as YamlScalar).Value == "GlowNormalSpecularMap");
//                if (glow != null)
//                {
//                    var glows = (glow["resourcePath"] as YamlScalar).Value.Replace(":", "").Replace("/", "\\").Replace("\"", "").ToLower();
//                    if (!textures.ContainsKey(glows))
//                    {
//                        var sf = List.FirstOrDefault(x => x.FullName == glows);
//                        if (sf != null)
//                            using (var stream = sf.GetStream())
//                            {
//                                Texture2D tex = null;
//                                AlphaSubmarines.DDSLib.DDSFromStream(stream, device, 0, false, out  tex);
//                                textures[glows] = tex;
//                                //textures[glows] = DDSSuport.Load(GraphicsDevice, stream);
//                            }
//                    }
//                    if (textures.ContainsKey(glows))
//                        meshParts[i].GlowNormalSpecularMap = glows;
//                }
//                var pgs = resources.Cast<YamlMapping>().FirstOrDefault(x => (x["name"] as YamlScalar).Value == "PgsMap");
//                if (pgs != null)
//                {
//                    var pgss = (pgs["resourcePath"] as YamlScalar).Value.Replace(":", "").Replace("/", "\\").Replace("\"", "").ToLower();
//                    if (!textures.ContainsKey(pgss))
//                    {
//                        var sf = List.FirstOrDefault(x => x.FullName == pgss);
//                        if (sf != null)
//                            using (var stream = sf.GetStream())
//                            {
//                                Texture2D tex = null;
//                                AlphaSubmarines.DDSLib.DDSFromStream(stream, device, 0, false, out  tex);
//                                textures[pgss] = tex;
//                                //textures[pgss] = DDSSuport.Load(GraphicsDevice, stream);
//                            }
//                    }
//                    if (textures.ContainsKey(pgss))
//                        meshParts[i].Pgs = pgss;
//                }
//                var mask = resources.Cast<YamlMapping>().FirstOrDefault(x => (x["name"] as YamlScalar).Value == "MaskMap");
//                if (mask != null)
//                {
//                    var masks = (mask["resourcePath"] as YamlScalar).Value.Replace(":", "").Replace("/", "\\").Replace("\"", "").ToLower();
//                    if (!textures.ContainsKey(masks))
//                    {
//                        var sf = List.FirstOrDefault(x => x.FullName == masks);
//                        if (sf != null)
//                            using (var stream = sf.GetStream())
//                            {
//                                Texture2D tex = null;
//                                AlphaSubmarines.DDSLib.DDSFromStream(stream, device, 0, false, out  tex);
//                                textures[masks] = tex;
//                                //textures[masks] = DDSSuport.Load(GraphicsDevice, stream);
//                            }
//                    }
//                    if (textures.ContainsKey(masks))
//                        meshParts[i].MaskMap = masks;
//                }
//                //var mask = resources.Cast<YamlMapping>().FirstOrDefault(x => (x["name"] as YamlScalar).Value == "MaterialDiffuseColor");
//                var dc = parameters.Cast<YamlMapping>().FirstOrDefault(x => (x["name"] as YamlScalar).Value == "MaterialDiffuseColor");
//                if (dc != null)
//                {
//                    try
//                    {
//                        meshParts[i].MaterialDiffuseColor = (dc["value"] as YamlSequence).Cast<YamlScalar>().Select(x => x.NativeObject is double ? (float)(double)x.NativeObject : (float)(long)x.NativeObject).ToArray();
//                    }
//                    catch
//                    {
//                        try
//                        {
//                            meshParts[i].MaterialDiffuseColor[0] = (float)(double)(dc["v1"] as YamlScalar).NativeObject;
//                            meshParts[i].MaterialDiffuseColor[1] = (float)(double)(dc["v2"] as YamlScalar).NativeObject;
//                            meshParts[i].MaterialDiffuseColor[2] = (float)(double)(dc["v3"] as YamlScalar).NativeObject;
//                        }
//                        catch { }
//                    }
//                }
//                //dynamic ms = parameters.FirstOrDefault(x => x.name == "\"MaskDiffuseColor\"");
//                var ms = parameters.Cast<YamlMapping>().FirstOrDefault(x => (x["name"] as YamlScalar).Value == "MaskDiffuseColor");
//                if (ms != null)
//                {
//                    try
//                    {
//                        meshParts[i].MaterialDiffuseColor = (ms["value"] as YamlSequence).Cast<YamlScalar>().Select(x => x.NativeObject is double ? (float)(double)x.NativeObject : (float)(long)x.NativeObject).ToArray();
//                    }
//                    catch
//                    {
//                        try
//                        {
//                            meshParts[i].MaterialDiffuseColor[0] = (float)(double)(ms["v1"] as YamlScalar).NativeObject;
//                            meshParts[i].MaterialDiffuseColor[1] = (float)(double)(ms["v2"] as YamlScalar).NativeObject;
//                            meshParts[i].MaterialDiffuseColor[2] = (float)(double)(ms["v3"] as YamlScalar).NativeObject;
//                        }
//                        catch { }
//                    }
//                }
//                //dynamic gc = parameters.FirstOrDefault(x => x.name == "\"GlowColor\"");
//                var gc = parameters.Cast<YamlMapping>().FirstOrDefault(x => (x["name"] as YamlScalar).Value == "GlowColor");
//                if (gc != null)
//                {
//                    try
//                    {
//                        meshParts[i].MaterialDiffuseColor = (gc["value"] as YamlSequence).Cast<YamlScalar>().Select(x => x.NativeObject is double ? (float)(double)x.NativeObject : (float)(long)x.NativeObject).ToArray();
//                    }
//                    catch
//                    {
//                        try
//                        {
//                            meshParts[i].MaterialDiffuseColor[0] = (float)(double)(gc["v1"] as YamlScalar).NativeObject;
//                            meshParts[i].MaterialDiffuseColor[1] = (float)(double)(gc["v2"] as YamlScalar).NativeObject;
//                            meshParts[i].MaterialDiffuseColor[2] = (float)(double)(gc["v3"] as YamlScalar).NativeObject;
//                        }
//                        catch { }
//                    }
//                }
//            }
//            try
//            {
//                //string ffs = 
//                var ff = (redobject["boundingSphereCenter"] as YamlSequence).Cast<YamlScalar>().Select(x => x.NativeObject is double ? (float)(double)x.NativeObject : (float)(long)x.NativeObject).ToArray();
//                modelCenter = new Vector3(ff[0], ff[1], ff[2]);
//            }
//            catch { modelCenter = new Vector3(0, 0, 0); }
//            var x1 = (redobject["boundingSphereRadius"] as YamlScalar);
//            modelRadius = x1.NativeObject is double ? (float)(double)x1.NativeObject : (float)(long)x1.NativeObject;
//        }


//        [StructLayout(LayoutKind.Sequential)]
//        public struct MVPTNTB : IVertexType
//        {
//            public MVPTNTB(Vector3 p, Vector3 n, Vector3 tg, Vector3 bn, Vector2 t)
//                : this()
//            {
//                Position = p;
//                TexCoord = t;
//                Normal = n;
//                Tangent = tg;
//                Binormal = bn;
//            }
//            public Vector3 Position;
//            public Vector3 Normal;
//            public Vector3 Tangent;
//            public Vector3 Binormal;
//            public Vector2 TexCoord;

//            public VertexDeclaration VertexDeclaration
//            {
//                get
//                {
//                    return new VertexDeclaration(new VertexElement(0, VertexElementFormat.Vector3, VertexElementUsage.Position, 0),
//                        new VertexElement(12, VertexElementFormat.Vector3, VertexElementUsage.Normal, 0),
//                        new VertexElement(24, VertexElementFormat.Vector3, VertexElementUsage.Tangent, 0),
//                        new VertexElement(36, VertexElementFormat.Vector3, VertexElementUsage.Binormal, 0),
//                        new VertexElement(48, VertexElementFormat.Vector2, VertexElementUsage.TextureCoordinate, 0)
//                        );
//                }
//            }
//        }

//        public VertexBuffer vertexBuffer = null;
//        public int VertexCount = 0;
//        public IndexBuffer IndexBuffer = null;

//        public class EVEMeshPart
//        {
//            //public IndexBuffer IndexBuffer;
//            public int TriangleCount;
//            public int TriangleFirst;
//            public string DiffuseMap;
//            public string GlowNormalSpecularMap;
//            public string Pgs;
//            public string MaskMap;
//            public float[] MaskDiffuseColor = new float[4] { 0.5f, 0.5f, 0.5f, 1f };
//            public float[] MaterialDiffuseColor = new float[4] { 0.5f, 0.5f, 0.5f, 1f };
//            public float[] GlowColor = new float[4] { 0f, 0f, 0f, 1f };
//            public bool IsTransparent;

//        }
//    }
//}
